﻿using Microsoft.Xna.Framework;
using PoolGame2.Physics;

namespace PoolGame2.Game
{
    class ReplayManager
    {
        private PhysicsRuntime physicsRuntime;
        private GameObject table;

        Vector3[] preShotBallPositions;
        Vector3[] postShotBallPositions;
        private Vector3 powerAndDirection;
        private Vector3 cueTipPosition;

        public bool IsShowingReplayMsg = false;
        public bool IsReplaying = false;

        private int replayFrame = 0;

        public ReplayManager(PhysicsRuntime pRuntime, GameObject pTable)
        {
            physicsRuntime = pRuntime;
            table = pTable;
        }

        public void recordPreShotState()
        {
            CleanUpReplay();
            preShotBallPositions = new Vector3[16];
            foreach (Ball ball in physicsRuntime.getState().getBalls())
            {
                preShotBallPositions[ball.getNumber()] = ball.getPosition();
            }
            IsShowingReplayMsg = false;
        }

        public void recordPostShotState()
        {
            postShotBallPositions = new Vector3[16];

            foreach (Ball ball in physicsRuntime.getState().getBalls())
            {
                postShotBallPositions[ball.getNumber()] = ball.getPosition();
            }
            IsShowingReplayMsg = true;
        }

        public void recordCueBallStrike(Vector3 x, Vector3 r)
        {
            powerAndDirection = x;
            cueTipPosition = r;
        }

        public void StartReplay()
        {
            if (preShotBallPositions != null && postShotBallPositions != null)
            {
                IsReplaying = true;
                IsShowingReplayMsg = false;
            }
        }

        public void UpdateReplay(GameTime time)
        {
            if (IsReplaying)
            {
                if (replayFrame == 0)
                {
                    // First frame: set up balls in pre-shot positions
                    for (int i = 0; i < table.getChildCount(); i++)
                    {
                        GameObject gameObj = table.getChild(i);
                        if (gameObj.getPhysicsObject() is Ball)
                        {
                            Ball ball = (Ball)gameObj.getPhysicsObject();
                            ball.setPosition(preShotBallPositions[ball.getNumber()]);
                        }
                    }
                }

                if (replayFrame == 30)
                {
                    // Replay shot after 30 frames
                    for (int i = 0; i < table.getChildCount(); i++)
                    {
                        GameObject gameObj = table.getChild(i);
                        if (gameObj.getPhysicsObject() is Ball)
                        {
                            Ball ball = (Ball)gameObj.getPhysicsObject();
                            if (ball.GetBallType() == BallType.CUE_BALL)
                            {
                                ball.Strike(powerAndDirection, cueTipPosition);
                                break;
                            }
                        }
                    }
                }
                if (replayFrame > 40 && physicsRuntime.AreBallsMoving() == false)
                {
                    // Balls have stopped moving: reposition balls in post shot position
                    for (int i = 0; i < table.getChildCount(); i++)
                    {
                        GameObject gameObj = table.getChild(i);
                        if (gameObj.getPhysicsObject() is Ball)
                        {
                            Ball ball = (Ball)gameObj.getPhysicsObject();
                            ball.setPosition(postShotBallPositions[ball.getNumber()]);
                        }
                    }
                    CleanUpReplay();
                }
                replayFrame++;
            }
        }

        private void CleanUpReplay()
        {
            preShotBallPositions = null;
            postShotBallPositions = null;
            IsReplaying = false;
            replayFrame = 0;
        }
    }
}